package com.iwhalecloud.citybrain.flow.platform.manager.infrastructure.repository;

import java.util.Collections;
import java.util.Date;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.iwhalecloud.citybrain.flow.platform.manager.application.utils.StringUtils;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.model.User;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.model.tenant.FlowTenantAddVo;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.model.tenant.FlowTenantInfoVo;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.model.tenant.FlowTenantQueryVo;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.model.tenant.FlowTenantSimpleInfoVo;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.model.tenant.FlowTenantUpdateVo;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.repository.FlowTenantRepository;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.repository.InitCreatorRepository;
import com.iwhalecloud.citybrain.flow.platform.manager.domain.repository.UserRepository;
import com.iwhalecloud.citybrain.flow.platform.manager.infrastructure.entities.FlowTenantInfo;
import com.iwhalecloud.citybrain.flow.platform.manager.infrastructure.entities.FlowTenantInfoExample;
import com.iwhalecloud.citybrain.flow.platform.manager.infrastructure.mapper.FlowTenantInfoDAO;
import org.apache.commons.collections4.CollectionUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

/**
 * @author lilh
 * @date 2019-01-22 14:44
 */
@Repository
public class FlowTenantRepositoryImpl implements FlowTenantRepository {

    private Logger logger = LoggerFactory.getLogger(this.getClass());

    @Autowired
    private FlowTenantInfoDAO flowTenantInfoDAO;

    @Autowired
    private InitCreatorRepository initCreatorRepository;

    @Autowired
    private UserRepository userRepository;

    @Override
    public int insert(FlowTenantAddVo flowTenantAddVo) {
        FlowTenantInfo entity = new FlowTenantInfo();
        BeanUtils.copyProperties(flowTenantAddVo, entity);
        FlowTenantInfoExample example = new FlowTenantInfoExample();
        example.createCriteria().andTenantNameEqualTo(entity.getTenantName());
        List<FlowTenantInfo> list = flowTenantInfoDAO.selectByExample(example);
        if (CollectionUtils.isNotEmpty(list)) {
            return 0;
        }
        example.clear();
        example.createCriteria().andTenantCodeEqualTo(entity.getTenantCode());
        list = flowTenantInfoDAO.selectByExample(example);
        if (CollectionUtils.isNotEmpty(list)) {
            return 0;
        }
        initCreatorRepository.init(entity);
        flowTenantInfoDAO.insertSelective(entity);
        return entity.getId();
    }

    @Override
    public PageInfo<FlowTenantInfoVo> list(FlowTenantQueryVo queryVo) {
        User user = userRepository.getCurrentUser();
        PageHelper.startPage(queryVo.getPageNum(), queryVo.getPageSize(), true);
        PageInfo<FlowTenantInfoVo> result = new PageInfo<>();
        PageInfo<FlowTenantInfo> tmp = new PageInfo<>();
        tmp = new PageInfo<>(flowTenantInfoDAO.selectByQuery(queryVo));

        result.setPageNum(tmp.getPageNum());
        result.setPageSize(tmp.getPageSize());
        result.setTotal(tmp.getTotal());
        if (CollectionUtils.isNotEmpty(tmp.getList())) {
            result.setList(tmp.getList().stream().map(this::convert).collect(Collectors.toList()));
        }
        return result;
    }

    @Override
    public int update(FlowTenantUpdateVo flowTenantUpdateVo) {
        FlowTenantInfo exist = flowTenantInfoDAO.selectByPrimaryKey(flowTenantUpdateVo.getId());
        if (Objects.isNull(exist)) {
            logger.error("更新的租户{}不存在", flowTenantUpdateVo.getId());
            return 0;
        }
        FlowTenantInfoExample tenantInfoExample = new FlowTenantInfoExample();
        // 判断租户编码是否有修改
        if (StringUtils.isNotEmpty(flowTenantUpdateVo.getTenantCode())
                && !Objects.equals(exist.getTenantCode(), flowTenantUpdateVo.getTenantCode())) {
            tenantInfoExample.createCriteria().andTenantCodeEqualTo(flowTenantUpdateVo.getTenantCode());
            List<FlowTenantInfo> tenantInfos = flowTenantInfoDAO.selectByExample(tenantInfoExample);
            if (CollectionUtils.isNotEmpty(tenantInfos)) {
                //编码已经存在
                logger.error("编码{}已经存在", flowTenantUpdateVo.getTenantCode());
                return 0;
            }
        } else {
            flowTenantUpdateVo.setTenantCode(null);
        }
        // 判断租户名称是否有修改
        if (StringUtils.isNotEmpty(flowTenantUpdateVo.getTenantName())
                && !Objects.equals(exist.getTenantName(), flowTenantUpdateVo.getTenantName())) {
            tenantInfoExample.clear();
            tenantInfoExample.createCriteria().andTenantNameEqualTo(flowTenantUpdateVo.getTenantName());
            List<FlowTenantInfo> tenantInfos = flowTenantInfoDAO.selectByExample(tenantInfoExample);
            if (CollectionUtils.isNotEmpty(tenantInfos)) {
                return 0;
            }
        } else {
            flowTenantUpdateVo.setTenantName(null);
        }
        FlowTenantInfo entity = new FlowTenantInfo();
        BeanUtils.copyProperties(flowTenantUpdateVo, entity);
        entity.setUpdateTime(new Date());
        flowTenantInfoDAO.updateByPrimaryKeySelective(entity);
        return entity.getId();
    }

    @Override
    public Boolean delete(Integer id) {
        //todo 权限校验
        int count = flowTenantInfoDAO.deleteByPrimaryKey(id);
        return count > 0;
    }

    @Override
    public FlowTenantInfoVo detail(Integer id) {
        return convert(flowTenantInfoDAO.selectByPrimaryKey(id));
    }

    @Override
    public List<FlowTenantSimpleInfoVo> listTenants(List<Integer> tenantIds) {
        if (CollectionUtils.isEmpty(tenantIds)) {
            return Collections.emptyList();
        }
        FlowTenantInfoExample query = new FlowTenantInfoExample();
        query.createCriteria().andIdIn(tenantIds);
        List<FlowTenantInfo> flowTenantInfos = flowTenantInfoDAO.selectByExample(query);
        return flowTenantInfos.stream().map(item -> {
            FlowTenantSimpleInfoVo tmp = new FlowTenantSimpleInfoVo();
            BeanUtils.copyProperties(item, tmp);
            return tmp;
        }).collect(Collectors.toList());
    }

    private FlowTenantInfoVo convert(FlowTenantInfo entity) {
        if (Objects.isNull(entity)) {
            return null;
        }

        FlowTenantInfoVo result = new FlowTenantInfoVo();
        BeanUtils.copyProperties(entity, result);
        return result;
    }


}
